package com.jeesite.modules.storage.util;

import cn.jiguang.common.ClientConfig;
import cn.jiguang.common.resp.APIConnectionException;
import cn.jiguang.common.resp.APIRequestException;
import cn.jiguang.common.resp.DefaultResult;
import cn.jpush.api.JPushClient;
import cn.jpush.api.device.TagAliasResult;
import cn.jpush.api.push.PushResult;
import cn.jpush.api.push.model.Message;
import cn.jpush.api.push.model.Options;
import cn.jpush.api.push.model.Platform;
import cn.jpush.api.push.model.PushPayload;
import cn.jpush.api.push.model.audience.Audience;
import cn.jpush.api.push.model.notification.IosNotification;
import cn.jpush.api.push.model.notification.Notification;
import com.jeesite.common.config.Global;
import ytx.org.apache.http.HttpStatus;

import java.util.*;

/**
 * @Author: starmile
 * @Description:
 * @Create: 2020-02-12 11:51
 **/
public class JPushUtil {
    private static String appKey = Global.getConfig("storage.jpush.appKey");
    private static String masterSecret = Global.getConfig("storage.jpush.masterSecret");

    /**
     * 快速推送全平台消息
     * @param massage
     * @return
     */
    public static Boolean pushAll(String massage) {
        PushPayload pushPayload = PushPayload.alertAll(massage);
        return push(pushPayload);
    }

    /**
     * 推送安卓平台消息
     * @param tag
     * @param massage
     * @param title
     * @return
     */
    public static Boolean pushAndroidByTag(String tag, String title, String massage) {
        List<String> tags = new ArrayList<>();
        tags.add(tag);
        return pushAndroid(tags, title, massage);
    }

    /**
     * 推送ios平台消息
     * @param tag
     * @param massage
     * @param title
     * @return
     */
    public static Boolean pushIosByTag(String tag, String title, String massage) {
        List<String> tags = new ArrayList<>();
        tags.add(tag);
        return pushIos(tags, title, massage);
    }

    /**
     * 推送安卓平台消息
     * @param registrationId
     * @param massage
     * @param title
     * @return
     */
    public static Boolean pushAndroidByRegistrationId(String registrationId, String title, String massage) {
        List<String> tags = getTags(registrationId);
        return pushAndroid(tags, title, massage);
    }

    /**
     * 推送ios平台消息
     * @param registrationId
     * @param massage
     * @param title
     * @return
     */
    public static Boolean pushIosByRegistrationId(String registrationId, String title, String massage) {
        List<String> tags = getTags(registrationId);
        return pushIos(tags, title, massage);
    }

    /**
     * 推送安卓平台消息
     * @param tags
     * @param title
     * @param massage
     * @return
     */
    public static Boolean pushAndroid(Collection<String> tags, String title, String massage) {
        PushPayload pushPayload = PushPayload.newBuilder()
                .setPlatform(Platform.android())
                .setAudience(Audience.tag(tags))
                .setNotification(Notification.android(massage, title, null))
                .build();
        return push(pushPayload);
    }

    /**
     * 推送ios平台消息
     * @param tags
     * @param title
     * @param massage
     * @return
     */
    private static Boolean pushIos(Collection<String> tags, String title, String massage) {

        PushPayload pushPayload = PushPayload.newBuilder()
                .setPlatform(Platform.ios())
                .setAudience(Audience.tag_and(tags))
                .setNotification(Notification.newBuilder()
                        .addPlatformNotification(IosNotification.newBuilder()
                                .setAlert(title)
                                .setBadge(1)
                                .setSound("happy")
                                .addExtra("from", "JPush")
                                .build())
                        .build())
                .setMessage(Message.content(massage))
                .setOptions(Options.newBuilder()
                        .setApnsProduction(true)
                        .build())
                .build();
        return push(pushPayload);
    }

    /**
     * 推送消息
     * @param payload
     */
    private static Boolean push(PushPayload payload) {
        JPushClient jpushClient = new JPushClient(masterSecret, appKey, null, ClientConfig.getInstance());

        try {
            PushResult result = jpushClient.sendPush(payload);
            if (result.statusCode == 0) {
                return true;
            }
            //log.info("极光推送结果: " + result);
        } catch (APIConnectionException e) {
            // Connection error, should retry later
            //log.error("连接错误，应稍后重试！", e);

        } catch (APIRequestException e) {
            // Should review the error, and fix the request
            //log.error("极光推送出现错误！", e);
            //log.info("HTTP Status: " + e.getStatus());
            //log.info("Error Code: " + e.getErrorCode());
            //log.info("Error Message: " + e.getErrorMessage());
        }
        return false;
    }

    public static Boolean registeredTag(String registrationId, String alias, Set<String> tags){
        JPushClient jpushClient = new JPushClient(masterSecret, appKey);
        try {
            DefaultResult result =  jpushClient.updateDeviceTagAlias(registrationId, alias, tags, null);
            return result.isResultOK();
        } catch (APIConnectionException e) {
            e.printStackTrace();
        } catch (APIRequestException e) {
            e.printStackTrace();
        }
        return false;
    }

    public static List<String> getTags(String registrationId){
        JPushClient jpushClient = new JPushClient(masterSecret, appKey);
        try {
            TagAliasResult result = jpushClient.getDeviceTagAlias(registrationId);
            if (result.tags.size() == 0) {
                Set<String> tags = new HashSet<>();
                tags.add(UUID.randomUUID().toString().replace("-",""));
                registeredTag(registrationId, "", tags);
                return new ArrayList<>(tags);
            }
            return result.tags;
        } catch (APIConnectionException e) {
            e.printStackTrace();
        } catch (APIRequestException e) {
            e.printStackTrace();
        }
        return null;
    }
}
